﻿using Manon.Admin.ApplicationCore.Common;
using Manon.Admin.ApplicationCore.Infrastructure;
using Manon.Admin.Web.ApplicationCore.Dtos.Role;
using Manon.Admin.Web.ApplicationCore.Entities;
using Manon.Admin.Web.ApplicationCore.Interfaces;
using Manon.Core.IOC;
using Manon.Core.Commons;
using Manon.Repository;
using Manon.Repository.Collections;
using Microsoft.EntityFrameworkCore;
using Microsoft.Extensions.Logging;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Linq.Expressions;
using System.Threading.Tasks;

namespace Manon.Admin.Web.ApplicationCore.Services
{
    public class RoleService : IRoleService
    {
        /// <summary>
        /// 获取角色分页列表
        /// </summary>
        /// <param name="Input"></param>
        /// <returns></returns>
        public async Task<IPagedList<RoleOutput>> GetRolePageList(GetRolePageListInput Input)
        {
            var logger = Resolver.GetService<ILogger<UserService>>();
            try
            {

                var unitOfWork = Resolver.GetService<IUnitOfWork<AdminDbContext>>();

                var result = await unitOfWork.GetRepository<Roles>()
                    .GetQuery()
                    .WhereIf(!string.IsNullOrEmpty(Input.RoleName), e => e.RoleName.Contains(Input.RoleName))
                    .WhereIf(Input.Enabled.HasValue, e => e.Enabled == Input.Enabled.Value)
                    .ToPagedListAsync<RoleOutput, Roles>(Input);
                return result;
            }
            catch (Exception ex)
            {
                logger.LogError("获取角色分页列表异常", ex);
                throw;
            }
        }


        /// <summary>
        /// 获取角色信息
        /// </summary>
        /// <param name="Input"></param>
        /// <returns></returns>
        public async Task<RoleOutput> GetRoleById(int RoleId)
        {
            if (RoleId == 0) return new RoleOutput() { Enabled = true };

            var logger = Resolver.GetService<ILogger<UserService>>();
            try
            {


                var unitOfWork = Resolver.GetService<IUnitOfWork<AdminDbContext>>();

                var result = await unitOfWork.GetRepository<Roles>().FindAsync(RoleId);
                return result.ConvertTo<Roles, RoleOutput>();
            }
            catch (Exception ex)
            {
                logger.LogError("获取角色信息异常", ex);
                throw;
            }
        }

        /// <summary>
        /// 保存角色信息
        /// </summary>
        /// <param name="Input"></param>
        /// <returns></returns>
        public async Task<Result> SaveRole(SaveRoleInput Input)
        {
            var logger = Resolver.GetService<ILogger<RoleService>>();
            try
            {
                var identityUser = Resolver.GetService<IIdentityUser>();
                var unitOfWork = Resolver.GetService<IUnitOfWork<AdminDbContext>>();
                var repos = unitOfWork.GetRepository<Roles>();
                var result = await repos.FindAsync(Input.Id);
                if (result == null)
                {
                    result = new Roles();
                    result.CreateTime = DateTime.Now;
                    result.Enabled = true;
                    result.UpdateTime = DateTime.Now;
                    result.RoleName = Input.RoleName;
                    result.OrderIndex = Input.OrderIndex;
                    result.Remark = Input.Remark;
                    result.RoleCode = Input.RoleCode;
                    result.CreateBy = identityUser.UserId;
                    result.UpdateBy = identityUser.UserId;
                    await repos.InsertAsync(result);
                }
                else
                {
                    result.Enabled = Input.Enabled;
                    result.UpdateTime = DateTime.Now;
                    result.RoleName = Input.RoleName;
                    result.OrderIndex = Input.OrderIndex;
                    result.Remark = Input.Remark;
                    result.RoleCode = Input.RoleCode;
                    result.UpdateBy = identityUser.UserId;
                    repos.Update(result);
                }
                await unitOfWork.SaveChangesAsync();
                return Result.Successed("保存成功!");
            }
            catch (Exception ex)
            {
                logger.LogError("保存角色信息异常", ex);
                throw;
            }
        }


        /// <summary>
        /// 设置角色是否可用
        /// </summary>
        /// <param name="Input"></param>
        /// <returns></returns>
        public async Task<Result> SetEnabled(SetRoleEnabledInput Input)
        {
            var logger = Resolver.GetService<ILogger<RoleService>>();
            try
            {

                var unitOfWork = Resolver.GetService<IUnitOfWork<AdminDbContext>>();

                var role = await unitOfWork.GetRepository<Roles>().FindAsync(Input.RoleId);
                if (role == null) return null;
                role.Enabled = Input.Enabled;
                await unitOfWork.SaveChangesAsync();
                return Result.Successed("设置成功!");

            }
            catch (Exception ex)
            {
                logger.LogError("设置角色是否可用异常", ex);
                throw;
            }
        }


        /// <summary>
        /// 获取角色简要信息列表
        /// </summary>
        /// <returns></returns>
        public async Task<List<SimpleRoleOutput>> GetSimpleRoleListAsync()
        {
            var logger = Resolver.GetService<ILogger<RoleService>>();
            try
            {
                List<SimpleRoleOutput> list = new List<SimpleRoleOutput>();

                var unitOfWork = Resolver.GetService<IUnitOfWork<AdminDbContext>>();
                var reops = unitOfWork.GetRepository<Roles>();

                var result = await reops.GetAll().OrderBy(n => n.OrderIndex).ThenBy(n => n.Id).ToListAsync();
                if (result == null)
                {
                    return list;
                }

                foreach (var item in result)
                {
                    list.Add(new SimpleRoleOutput()
                    {
                        RoleId = item.Id.ToString(),
                        RoleName = item.RoleName,
                        Enabled = item.Enabled
                    });
                }
                return list;


            }
            catch (Exception ex)
            {
                logger.LogError("获取环境变量列表异常", ex);
                throw;
            }
        }

        /// <summary>
        /// 保存用户角色
        /// </summary>
        /// <param name="Input"></param>
        /// <returns></returns>
        public async Task<Result> BandRoles(BandRoleInput Input)
        {
            var logger = Resolver.GetService<ILogger<UserService>>();
            try
            {

                var unitOfWork = Resolver.GetService<IUnitOfWork<AdminDbContext>>();
                var repos = unitOfWork.GetRepository<UserRoles>();

                var existsRoles = repos.GetAllByWhere(n => n.UserId == Input.UserId);
                repos.Delete(existsRoles);

                List<UserRoles> listUserRoles = new List<UserRoles>();

                if (Input.RoleIds != null && Input.RoleIds.Count != 0)
                {
                    foreach (var item in Input.RoleIds)
                    {
                        UserRoles ur = new UserRoles();
                        ur.CreateTime = DateTime.Now;
                        ur.RoleId = int.Parse(item);
                        ur.UpdateTime = DateTime.Now;
                        ur.UserId = Input.UserId;
                        listUserRoles.Add(ur);
                    }

                    await repos.InsertAsync(listUserRoles);
                }

                await unitOfWork.SaveChangesAsync();
                return Result.Successed("设置成功!");

            }
            catch (Exception ex)
            {
                logger.LogError("保存用户角色异常", ex);
                throw;
            }
        }

        /// <summary>
        /// 获取用户角色id集合
        /// </summary>
        /// <param name="Input"></param>
        /// <returns></returns>
        public async Task<List<string>> GetUserBandRoles(int UserId)
        {
            var logger = Resolver.GetService<ILogger<UserService>>();
            try
            {
                var unitOfWork = Resolver.GetService<IUnitOfWork<AdminDbContext>>();
                var repos = unitOfWork.GetRepository<UserRoles>();

                var userRoles = await repos.GetAllByWhere(n => n.UserId == UserId).ToListAsync();

                return userRoles?.Select(n => n.RoleId.ToString()).ToList();

            }
            catch (Exception ex)
            {
                logger.LogError("获取用户角色id集合异常", ex);
                throw;
            }
        }




        /// <summary>
        /// 获取角色菜单id集合
        /// </summary>
        /// <param name="Input"></param>
        /// <returns></returns>
        public async Task<List<string>> GetRoleMenuIds(int RoleId)
        {
            var logger = Resolver.GetService<ILogger<UserService>>();
            try
            {
                var unitOfWork = Resolver.GetService<IUnitOfWork<AdminDbContext>>();
                var repos = unitOfWork.GetRepository<RoleMenus>();

                var roleMenus = await repos.GetAllByWhere(n => n.RoleId == RoleId && n.MenuType == 3).ToListAsync();

                return roleMenus?.Select(n => n.MenuId.ToString()).ToList();

            }
            catch (Exception ex)
            {
                logger.LogError("获取角色菜单id集合异常", ex);
                throw;
            }
        }




        /// <summary>
        /// 保存角色菜单
        /// </summary>
        /// <param name="Input"></param>
        /// <returns></returns>
        public async Task<Result> BandRoleMenus(BandRoleMenusInput Input)
        {
            var logger = Resolver.GetService<ILogger<UserService>>();
            try
            {

                var unitOfWork = Resolver.GetService<IUnitOfWork<AdminDbContext>>();
                var repos = unitOfWork.GetRepository<RoleMenus>();

                var existsRoles = repos.GetAllByWhere(n => n.RoleId == Input.RoleId);
                repos.Delete(existsRoles);

                List<RoleMenus> listRoleMenus = new List<RoleMenus>();

                if (Input.Items != null && Input.Items.Count != 0)
                {
                    foreach (var item in Input.Items)
                    {
                        RoleMenus ur = new RoleMenus();
                        ur.CreateTime = DateTime.Now;
                        ur.RoleId = Input.RoleId;
                        ur.UpdateTime = DateTime.Now;
                        ur.MenuId = item.Id;
                        ur.MenuType = item.MenuType;
                        listRoleMenus.Add(ur);
                    }

                    await repos.InsertAsync(listRoleMenus);
                }

                await unitOfWork.SaveChangesAsync();
                return Result.Successed("设置成功!");

            }
            catch (Exception ex)
            {
                logger.LogError("保存角色菜单异常", ex);
                throw;
            }
        }



        /// <summary>
        /// 获取用户可访问的页面
        /// </summary>
        /// <param name="UserId"></param>
        /// <returns></returns>
        public async Task<List<string>> GetUserMenuIds()
        {
            var logger = Resolver.GetService<ILogger<UserService>>();
            try
            {
                var identityUser = Resolver.GetService<IIdentityUser>();
                int CurrentUserId = identityUser.UserId;
                var unitOfWork = Resolver.GetService<IUnitOfWork<AdminDbContext>>();

                IEnumerable<GetUserMenuIdsOutput> list = await unitOfWork.FromSqlAsync<GetUserMenuIdsOutput>($@"select  b.MenuId from user_roles a
                            join role_menus b on a.RoleId=b.RoleId
                            where b.MenuType in (1,2) and a.UserId={CurrentUserId} ");
                return list?.Select(n => n.MenuId).ToList();

            }
            catch (Exception ex)
            {
                logger.LogError("获取用户可访问的页面异常", ex);
                throw;
            }
        }


        /// <summary>
        /// 获取用户可访问的页面按钮
        /// </summary>
        /// <param name="UserId"></param>
        /// <returns></returns>
        public async Task<List<string>> GetUserMenuButtonIds()
        {
            var logger = Resolver.GetService<ILogger<UserService>>();
            try
            {
                var identityUser = Resolver.GetService<IIdentityUser>();
                int CurrentUserId = identityUser.UserId;
                var unitOfWork = Resolver.GetService<IUnitOfWork<AdminDbContext>>();

                IEnumerable<GetUserMenuIdsOutput> list = await unitOfWork.FromSqlAsync<GetUserMenuIdsOutput>($@"select  b.MenuId from user_roles a
                            join role_menus b on a.RoleId=b.RoleId
                            where b.MenuType =3 and a.UserId={CurrentUserId} ");
                return list?.Select(n => n.MenuId).ToList();

            }
            catch (Exception ex)
            {
                logger.LogError("获取用户可访问的页面按钮异常", ex);
                throw;
            }
        }
    }
}
